<?php
/*
 * @Author: 李明
 * @Date: 2021-12-29 10:28:36
 * @LastEditTime: 2022-01-20 15:22:34
 * @LastEditors: 李明
 * @Description:
 * @FilePath: /CRM2.0-PHP/app/Http/Controllers/order/AuditOrder/AuditOrderController.php
 * @山东壹零贰肆信息科技有限公司
 */

namespace App\Http\Controllers\order\AuditOrder;

use App\Http\Controllers\admin\BranchController;
use App\Http\Controllers\common\CommonFun;
use App\Http\Controllers\common\LMReturn;
use App\Http\Controllers\Controller;
use App\Http\Controllers\order\OrderController;
use App\Http\Controllers\order\OrderRecordController;
use App\Http\Controllers\WeChatService\WeChatServiceUtils;
use App\Http\Controllers\Utils;
use App\Http\Resources\Order\AuditOrder;
use App\Models\InterestRecord;
use App\Models\Order;
use App\Models\User;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;

class AuditOrderController extends Controller
{
    /**
     * @description: 查找初审和复审订单
     * @param {Request} $request
     * @return {*}
     */
    public function auditOrderList(Request $request)
    {
        try {
            //去验证token值
            $tokenInfo = json_decode($this->verifyTokenLm(), true);
            //判断传递过来的token的code码是否等于400  如果是400的话，提示token不正确
            if ($tokenInfo['code'] == 400) {
                return LMReturn::Error($tokenInfo['msg'], $tokenInfo['code']);
            }
            //接收前端传递过来的值
            $all = $request->all();
            $where = [];
            $worker_id = $tokenInfo['worker_id'];
            if (isset($all['audit_step'])) {
                $where[] = ['order.audit_step',  $all['audit_step']];
            } else {
                $where[] = ['order.audit_step',  '!=', '3'];
            }
            if (isset($all['manage_bm'])) {
                $bmidList = BranchController::queryBranchToWorkerID($worker_id, $all['manage_bm']);
            } else {
                $bmidList = BranchController::queryBranchToWorkerID($worker_id);
            }
            if (count($bmidList) == 0) {
                $where[] = ['order.worker_id', $worker_id];
            }
            if (isset($all['worker_id'])) { // 用于查询个人的待审核订单
                $where[] = ['order.worker_id', $all['worker_id']];
            }
            if (isset($all['contract_no'])) {
                $where[] = ['order.contract_no', $all['contract_no']];
            }
            if (isset($all['start_sign_time']) && isset($all['end_sign_time'])) {
                $where[] = ['order.sign_time', '>=', date('Y-m-d', strtotime($all['start_sign_time']))];
                $where[] = ['order.sign_time', '<=', date('Y-m-d', strtotime($all['end_sign_time']))];
            }
            if (isset($all['start_valid_time']) && isset($all['end_valid_time'])) {
                $where[] = ['order.valid_time', '>=', date('Y-m-d', strtotime($all['start_valid_time']))];
                $where[] = ['order.valid_time', '<=', date('Y-m-d', strtotime($all['end_valid_time']))];
            }
            if (isset($all['start_contract_end_date']) && isset($all['end_contract_end_date'])) {
                $where[] = ['order.contract_end_date', '>=', date('Y-m-d', strtotime($all['start_contract_end_date']))];
                $where[] = ['order.contract_end_date', '<=', date('Y-m-d', strtotime($all['end_contract_end_date']))];
            }
            $pageSize = isset($all['size']) ? $all['size'] : 15;
            $user_id_list = [];
            if (isset($all['user_name'])) {
                $user_id_list = json_decode(User::select('id')
                    ->where("name", 'like', '%' . $all['user_name'] . '%')->get(), true);
                $user_id_list = CommonFun::SelSqlArr('id', $user_id_list);
            }
            $order_status_list = ['2', '1'];/*订单状态 -1草稿， 1是待付款  2是审核中   3是待生效(弃用)  4是已生效 5是拒绝  6是已结束  ,7废弃8提前终止*/
        } catch (\Throwable $th) {
            return LMReturn::Error('查询条件存在问题，请联系管理员', 'OC023');
        }

        try {
            $order_list = Order::with('branch')
                ->with('worker')
                ->with('user')
                ->with('bank_card.bank')
                ->with('families_money_records.working_family')
                // ->with('order_records')
                ->where($where)
                ->whereIn('order.order_status', $order_status_list)
                ->when(count($bmidList) > 0, function ($query) use ($bmidList) {
                    return $query->whereIn('order.branch_id', $bmidList);
                })
                ->when(isset($all['user_name']), function ($query) use ($user_id_list) {
                    return $query->whereIn('order.user_id', $user_id_list);
                })
                ->orderBy("order.update_time", "desc")
                ->paginate($pageSize);
        } catch (\Throwable $th) {
            return LMReturn::Error('查询存在问题，请联系管理员', 'OC020');
        }
        try {
            // 返回前端需要的数据
            $res_order_list = AuditOrder::collection($order_list);
            $return_datas = Utils::deal_page_resources($res_order_list, $order_list);
            return LMReturn::Success($return_datas);
        } catch (\Throwable $th) {
            return LMReturn::Error('数据存在问题，请联系管理员', 'AOCAOL1');
        }
    }
    /**
     * @description: 财务审核
     * @param {Request} $request
     * @return {*}
     */
    public function auditFinance(Request $request)
    {
        try {
            //去验证token值
            $tokenInfo = json_decode($this->verifyTokenLm(), true);
            //判断传递过来的token的code码是否等于400  如果是400的话，提示token不正确
            if ($tokenInfo['code'] == 400) {
                return LMReturn::Error($tokenInfo['msg'], $tokenInfo['code']);
            }
            $all = $request->all();
            $tl_pay_list = $all['tl_pay_list'];
        } catch (\Throwable $th) {
            return LMReturn::Error('传参存在错误', 'AOCAF1');
        }
        try {
        } catch (\Throwable $th) {
            return LMReturn::Error('财务审核失败', 'AOCAF2');
        }
    }
    /**
     * @description: 订单审核接口
     * @param {Request} $request
     * @return {*}
     */
    public function OrderAudit(Request $request)
    {
        try {
            //去验证token值
            $tokenInfo = json_decode($this->verifyTokenLm(), true);
            //判断传递过来的token的code码是否等于400  如果是400的话，提示token不正确
            if ($tokenInfo['code'] == 400) {
                return LMReturn::Error($tokenInfo['msg'], $tokenInfo['code']);
            }
            $all = $request->all();
            $audit_step = $all['audit_step']; // 审核步数 1初审，2复审
            $order_id = $all['order_id'];
            $is_audit = $all['is_first_instance']; // 是否通过审核 1是2否
            $remark = $all['remark'] ?? '';
            $order = Order::find($order_id);
            $product = $order->product;
            $user = $order->user;
            $audit_step_old = $order->audit_step;
            if ($audit_step != $audit_step_old) { //传过来的审核状态必须和现在的状态一致，不可以跳审
                return LMReturn::Error("请联系管理员,订单审核状态异常", 'OC035');
            } else if ($audit_step == '1') { //初审 必传传生效时间
                if ($is_audit == '1') { //通过审核必传传生效时间 如果拒绝不需要用生效时间 1同意 2拒绝
                    $valid_time = $all['valid_time'];
                }
            } else if ($audit_step == '2') { // 复审，生效时间取现有的生效时间。判断当前订单是否有生效时间
                $valid_time = $order->valid_time;
            } else {
                return LMReturn::Error("请联系管理员,订单无须审核", 'OC006');
            }

            $order_old_list = Order::where('contract_no', $order->contract_no)
                ->whereIn('order_status', [3, 4, 6])
                ->get();
            if (count($order_old_list) > 0 &&  $is_audit == '1') {
                return LMReturn::Error('已经存在已生效的相同合同号的订单，无法通过审核', 'OC013');
            }
        } catch (\Throwable $th) {
            return LMReturn::Error('传参存在错误', 'OC007');
        }

        try {
            DB::beginTransaction();
            // 首先处理拒绝审核，如果是拒绝直接改状态
            if ($is_audit == '2') { //拒绝审核 如果拒绝不需要用生效时间
                $auditRes = $this->denyOrder($order, $audit_step, $tokenInfo, $remark);
                DB::commit();
                return LMReturn::Success($auditRes['order'], '拒绝审核');
            } else { // 同意审核 通过审核
                if ($audit_step == '1') { // 初审
                    $auditRes = $this->agreeOrderOne($order, $product, $user, $tokenInfo, $all);
                    DB::commit();
                    return LMReturn::Success($auditRes['order'], '同意审核');
                } else if ($audit_step == '2') { // 复审
                    $fdd_sign_status = $order['fdd_sign_status'];
                    if ($fdd_sign_status == 5 || $fdd_sign_status == 6) {
                        return LMReturn::Error('本订单为电子签约订单，未签署完成，不可通过复审');
                    }
                    $oldOrderInterestRecordList = InterestRecord::Where('order_id', $order_id)->get();
                    if (count($oldOrderInterestRecordList) > 0) {
                        return LMReturn::Error('订单存在安全隐患，请联系技术人员，进行安全排查', 'OC010');
                    }
                    $auditRes = $this->agreeOrderTwo($order, $product, $user, $tokenInfo, $all, $order->branch_id);
                    DB::commit();
                    return LMReturn::Success($auditRes['order'], '同意审核');
                } else {
                    return LMReturn::Error('审核出现错误', 'OC004');
                }
            }
        } catch (\Throwable $th) {
            DB::rollBack();
            return LMReturn::Error('审核出现错误', 'OC005');
        }
    }


    /**
     * @description: 订单拒绝审核  返回false 代表操作成功 其他都代表有问题
     * @param {*} $order
     * @param {*} $audit_step
     * @param {*} $tokenInfo
     * @return {*}
     */
    public function denyOrder($order, $audit_step, $tokenInfo, $remark)
    {
        $order->order_status = '5'; // 订单状态  1是待付款  2是审核中   3是待生效  4是已生效 5是拒绝  6是已结束
        $order->is_first_instance = '2'; // 审核状态    1通过  2拒绝 3待审核
        $order->audit_step = '1'; // 拒绝审核之后， 审核步骤回到第一步
        $order->fdd_sign_status = 2;
        $order->contract_file = 2;
        if ($remark == '') {
            $remark = '订单拒绝，未填写原因';
        }
        //在记录表里面去添加
        $recordResutl = OrderRecordController::InsertOrderModelRecord($order, $tokenInfo, '1', $audit_step, '2', $remark);
        $order->save();
        $order['order_id'] = $order->id;
        $auditRes['recordResutl'] = $recordResutl;
        $auditRes['order'] = $order;
        return $auditRes;
    }

    /**
     * @description: 订单同意审核，通过审核
     * @param {*}
     * @return {*}
     */
    public function agreeOrderOne($order, $product, $user, $tokenInfo, $all)
    {

        //生效时间（是否传递在传参是否存在错误进行了判断）
        $valid_time = date('Y-m-d', strtotime($all['valid_time']));
        $orderEndTime = OrderController::calculateEndTime($all['valid_time'], $product)['contract_end_date'];
        // 赋值
        $order->contract_end_date = $orderEndTime; // 订单结束时间
        $order->valid_time = $valid_time; //   生效时间
        $order->order_status = '2'; // 订单状态  1是待付款  2是审核中   3是待生效  4是已生效 5是拒绝  6是已结束
        $order->audit_step = '2'; //初审通过审核，把步骤改成复审 1初审  2复审
        $order->save();
        $order['order_id'] = $order->id;
        //在记录表里面去添加审核成功的记录
        $recordResutl = OrderRecordController::InsertOrderModelRecord($order, $tokenInfo, '1', '1', '1');
        $auditRes['recordResutl'] = $recordResutl;
        $auditRes['order'] = $order;
        return $auditRes;
    }

    /**
     * @description:
     * @param {*} $order 同意审核 终审
     * @param {*} $product
     * @param {*} $user
     * @return {*}
     */
    public function agreeOrderTwo($order, $product, $user, $tokenInfo, $all, $branch_id)
    {
        $order_status = '4'; // 4已生效
        // 根据 身份证号，去判断用户是否为首单/新用户
        $oldUser = User::where("id_number", $user->id_number)
            ->where("is_first", "!=", "-1")
            ->first();
        if ($oldUser) // 如果不存在已经下单的用户，就代表是新用户，否则是老用户
        {
            $is_first = '2'; // -1是新用户未开单 1是新用户已开单  2是老用户
        } else {
            $is_first = '1'; // -1是新用户未开单 1是新用户已开单  2是老用户
        }
        // 如果是需要付款的订单，则进行插入付款记录
        if ($product->pay_type != '5') { // 付款方式  2自然月  4到期 5不付款
            // 如果是按月付款，根据付款间隔时长生成对应的付款记录
            $payLong = $product->pay_long;
            $longTime = $product->long_time; // 产品周期
            $orderMoney = $order->order_money; // 本金
            $order_id = $order->id;
            $endTime = date("Y-m-d", strtotime($order->contract_end_date)); // 到期时间
            $validTime = date("Y-m-d", strtotime($order->valid_time)); // 生效时间
            $rate = $product->rate;
            // 如果需要付款，判断是到期付款还是按月付款
            $resArr = [];
            // 插入之前先判断 是向上取整，还是向下取整
            // 插入订单打款记录
            if ($product->pay_type == '2') { //自然月
                $resArr = $this->createOrderMonthInterest($longTime, $payLong, $orderMoney, $rate, $validTime, $order_id, $endTime, $branch_id);
            } elseif ($product->pay_type == '4') { //到期付款
                $resArr = $this->createOrderEndPay($order_id, $endTime, $orderMoney, $rate, $longTime, $branch_id);
            }
        }
        // 赋值，
        $order->order_status = $order_status;
        $order->audit_step = '3';
        $order->is_first_instance = '1';
        $user->is_first = $is_first;
        if (isset($all['account_time'])) { // 到账时间
            $order->account_time = $all['account_time'];
        }
        if (isset($all['pay_list'])) {
            OrderController::OrderPayList($all['pay_list'], $order, 1, 5);
        }
        $user->save();
        $order->save();
        $order['order_id'] = $order->id;
        //在记录表里面去添加审核成功的记录
        $recordResutl = OrderRecordController::InsertOrderModelRecord($order, $tokenInfo, '1', '2', '1');
        $auditRes['recordInterestResutl'] = $resArr;
        $auditRes['recordResutl'] = $recordResutl;
        $auditRes['order'] = $order;
//        try {
//            // 通过审核在公众号后给客户发消息
//            $sta = WeChatServiceUtils::SendOrderEffect($order->contract_no, $user->public_open_id);
//        } catch (\Throwable $th) {
//        }
        return $auditRes;
    }

    /**
     * @description: 按月付款利息记录插入
     * @param {*}
     * @return {*}
     */
    public static function createOrderMonthInterest($longTime, $payLong, $orderMoney, $rate, $validTime, $orderID, $endTime, $branch_id)
    {
        $interestInfoArr = [];
        $payCount = $longTime / $payLong;
        for ($i = 0; $i < $payCount; $i++) {
            // 计算利息  = 金额*年利率/12*还款间隔
            $interest = $orderMoney * $rate / 12 * $payLong / 100;
            $nowYear = date("Y", strtotime($validTime)); // 当前年份
            $nowMonth = date("m", strtotime($validTime)); // 当前月份
            $newMonth = $nowMonth + $payLong * ($i + 1); //需要打款的月份
            $newYear = $nowYear;
            if ($newMonth > 12) { // 如果打款的月份超过 12月，则需要加取整的年份   月份需要减去对应的年数*24
                $nm = intval($newMonth / 12); // 取整
                $newYear = $nowYear + $nm;
                $newMonth = $newMonth - $nm * 12;
            } else {
                $newYear = $nowYear;
            }
            $day = date("d", strtotime($validTime)); // 当前日期
            $daynum = date("t", strtotime($newYear . "-" . $newMonth)); // 当前月份对应的天数
            if ($day <= $daynum) // 如果当前日期，小于当前月份的天数，则直接使用
            {
                $hk_date = $newYear . "-" . $newMonth . "-" . $day;
                $hk_date = date("Y-m-d", strtotime($hk_date));
            } else // 如果当前日期，大于当前月份的天数，则改成当前月份的最后一天
            {
                $hk_date = $newYear . "-" . $newMonth . "-" . $daynum;
                $hk_date = date("Y-m-d", strtotime($hk_date));
            }
            $interestRecodeInfo['order_id'] = $orderID; // 订单id
            $interestRecodeInfo['branch_id'] = $branch_id; // 部门id
            $interestRecodeInfo['num'] = $i + 1; // 第几期
            $interestRecodeInfo['num_all'] = $payCount; // 共多少期
            $interestRecodeInfo['date'] = $hk_date; // 还款日期
            $interestRecodeInfo['interest'] = round($interest, 2); // 月利息
            $interestRecodeInfo['money'] = 0; // 本金
            //            $interestRecodeInfo['payment_amount'] = round($interest, 2); // 应打款金额
            $interestRecodeInfo['is_exit'] = 2; // 是否提前终止  1是2否
            $interestRecodeInfo['create_time'] = date("Y-m-d H:i:s", time()); // 添加时间
            $interestRecodeInfo['type'] = 2; //是否成功计算   1是失败 2是正常计算  3是最后一次
            $interestRecodeInfo['status'] = 1; // 本期还款状态 1待还款 2已还款 3逾期未换
            $interestRecodeInfo['message_remind'] = -1; // 短信提醒次数
            if ($i > 0) {
                $interestInfoArr[$i - 1]['next_date'] = $hk_date; // 下次还款日期
            } else {
                $interestRecodeInfo['next_date'] = $hk_date; // 下次还款日期
            }
            if ($i == $payCount - 1) { //最后一期
                $interestRecodeInfo['date'] = $endTime; // 还款日期
                $interestInfoArr[$i - 1]['next_date'] = $endTime; // 下次还款日期
                $interestRecodeInfo['next_date'] = $endTime; // 下次还款日期
                $interestRecodeInfo['money'] = $orderMoney; // 本金
                $interestRecodeInfo['type'] = 3; //是否成功计算   1是失败 2是正常计算  3是最后一次
                $interestRecodeInfo['payment_amount'] = Utils::getNumRules($interest + $orderMoney, env('INTEGER_RULES'), env('KEEPS'));
            } else {
                $interestRecodeInfo['payment_amount'] = Utils::getNumRules($interest, env('INTEGER_RULES'), env('KEEPS'));
            }
            //            $interestRecodeInfo['payment_amount'] = ceil($interestRecodeInfo['interest']) + $interestRecodeInfo['money']; // 取整金额   ceil 向上取整  向下取整  floor
            $interestInfoArr[] = $interestRecodeInfo;
        }
        // 插入利息记录
        $resArr = [];
        foreach ($interestInfoArr as $keyInterest => $valueInterest) {
            $resArr[] = InterestRecord::create($valueInterest);
        }
        return $resArr;
    }

    /**
     * @description: 到期付款利息记录插入
     * @param {*}
     * @return {*}
     */
    public static function createOrderEndPay($orderID, $endTime, $orderMoney, $rate, $longTime, $branch_id)
    {
        $interestInfoArr = [];
        // 如果是到期付款 只需要生成一条记录
        // 2.0  需求修改为
        $interest = $orderMoney * $rate / 12 * $longTime / 100;
        $interestRecodeInfo['order_id'] = $orderID; // 订单id
        $interestRecodeInfo['branch_id'] = $branch_id;  // 部门id
        $interestRecodeInfo['date'] = $endTime; // 还款日期
        $interestRecodeInfo['interest'] = round($interest, 2); // 月利息
        $interestRecodeInfo['money'] = $orderMoney; // 本金
        $interestRecodeInfo['payment_amount'] = Utils::getNumRules($interest + $orderMoney, env('INTEGER_RULES'), env('KEEPS'));
        //        $interestRecodeInfo['payment_amount'] = ceil(round($interest, 2) + $orderMoney);
        $interestRecodeInfo['is_exit'] = 2; // 是否提前终止  1是2否
        $interestRecodeInfo['create_time'] = date("Y-m-d H:i:s", time()); // 添加时间
        $interestRecodeInfo['type'] = 3; //是否成功计算   1是失败 2是正常计算  3是最后一次
        $interestRecodeInfo['status'] = 1; // 本期还款状态 1待还款 2已还款 3逾期未换
        $interestRecodeInfo['message_remind'] = -1; // 短信提醒次数
        $interestRecodeInfo['next_date'] = $endTime; // 下次还款日期
        $interestRecodeInfo['num'] = 1; // 第几期
        $interestRecodeInfo['num_all'] = 1; // 共多少期
        //        $interestRecodeInfo['payment_amount'] = ceil($interestRecodeInfo['interest']) + $interestRecodeInfo['money']; // 取整金额
        $interestInfoArr[] = $interestRecodeInfo;
        // 插入利息记录
        $resArr = [];
        foreach ($interestInfoArr as $keyInterest => $valueInterest) {
            $resArr[] = InterestRecord::create($valueInterest);
        }
        return $resArr;
    }
}
